<template>
	<div class="container">
		<!-- 展示区域 -->
		<div class="map-container" ref="mapContainer" @click="handleMapClick" @mousemove="handleDrag"
			@mouseup="stopDrag" @mouseleave="stopDrag">

			<!-- 地图点位展示 -->
			<div v-for="point in points" :key="point.id" class="map-point" :style="pointStyle(point)"
				@mousedown="startDrag(point, $event)" @click="handlePointClick(point)" :class="{ 
                 selected: selectedPoint?.id === point.id,
                 dragging: isDragging,
                 [getPointClass(point.pointType)]: true
               }">
				<!-- <div class="point-label"> {{ point.pointName }} </div> -->
				<div class="point-label"> {{ point.pointName }} ({{ point.locationx }}, {{ point.locationy }})</div>
			</div>
		</div>

		<!-- 编辑区域 -->
		<div class="editor-panel" ref="editorPanel" @mousedown="startPanelDrag">
			<div class="info-card" v-if="selectedPoint">
				<h3>当前选中点位</h3>
				<div class="info-item">
					<label>名称：</label>
					<input v-model="selectedPoint.pointName" :disabled="!isEditing">
				</div>
				<div class="info-item">
					<label>ID：</label>
					<input v-model="selectedPoint.id" type="number" :disabled="true">
				</div>
				<div class="info-item">
					<label>类型：</label>
					<select v-model="selectedPoint.pointType" :disabled="!isEditing" style="width: 55%;">
						<option value="CAR">车辆</option>
						<option value="WAREHOUSE">仓库</option>
						<option value="TRANSFER">转运点</option>
					</select>
				</div>
				<div class="info-item">
					<label>坐标 X：</label>
					<input v-model="selectedPoint.locationx" type="number" :disabled="!isEditing">
				</div>
				<div class="info-item">
					<label>坐标 Y：</label>
					<input v-model="selectedPoint.locationy" type="number" :disabled="!isEditing">
				</div>
				<div class="info-item">
					<label>节点ID：</label>
					<input v-model="selectedPoint.nodeId" :disabled="!isEditing">
				</div>

				<div class="button-group">
					<button v-if="!isEditing" @click="confirmDelete" class="delete-btn">
						🗑️ 删除
					</button>
					<button v-if="!isEditing" @click="startEditing" class="edit-btn">
						✏️ 编辑
					</button>
					<template v-else>
						<button @click="saveChanges" class="save-btn">💾 保存</button>
						<button @click="cancelEditing" class="cancel-btn">❌ 取消</button>
					</template>
				</div>
			</div>
			<div v-else class="empty-tip">
				<ol>
					<li>新增点位：鼠标左键单击</li>
					<li>修改点位：拖动或单击击</li>
					<li>删除点位：选中后可编辑</li>
					<li>拖动点位修改位置和排版</li>
				</ol>
			</div>
		</div>
	</div>
</template>

<script setup>
	import {
		ref,
		reactive,
		onMounted,
		computed,
		onBeforeUnmount
	} from 'vue';
	import {
		ElMessage
	} from 'element-plus';
	import {
		wcao,
		post,
		rgvpost
	} from "@/http";
	import axios from 'axios';
	import './css/huo02203.css';
	// 拖拽相关状态
	const isDragging = ref(false);
	const draggingPoint = ref(null);
	const dragStartPos = reactive({
		x: 0,
		y: 0
	});
	const mapContainer = ref(null);

	// 点位数据
	// 点位数据
	let maxPointId = 3;
	const points = ref([]);
	const loadPoints = async () => {
		try {
			let response = await axios.post('/points/getAll'); // 替换为实际的 API 地址
			console.log('加载点位个数:' + response.data.length);
			points.value = response.data;
			// 调试：打印实际数据类型
			// console.log('响应数据类型:', typeof response.data, '内容:', JSON.stringify(response.data));
			// 处理非数组响应
			if (!Array.isArray(response.data)) {
				throw new Error(`无效的响应类型，预期数组，实际得到: ${typeof response.data}`);
			}
			// 数据转换
			let validPoints = response.data
				.map(p => ({
					id: Number(p.id),
					pointName: p.pointName || '未命名',
					pointType: p.pointType || 'DEFAULT',
					locationx: Number(p.locationX) || 0,
					locationy: Number(p.locationY) || 0,
					nodeId: p.nodeId
				}))
				.filter(p => Number.isInteger(p.id) && p.id > 0);

			// 更新状态
			points.value = validPoints;
			maxPointId = validPoints.length > 0 ?
				Math.max(...validPoints.map(p => p.id)) :
				0;

		} catch (error) {
			console.log('加载失败:', error);

			points.value = [{
				id: 1,
				pointName: '示例车-1',
				pointType: 'CAR', // 新增类型字段
				locationx: 50, // 原x
				locationy: 50, // 原y
				nodeId: 'rgv.rgv.sdf1' // 新增节点ID
			}, {
				id: 2,
				pointName: '示例转-1',
				pointType: 'TRANSFER', // 新增类型字段
				locationx: 50, // 原x
				locationy: 100, // 原y
				nodeId: 'rgv.rgv.sdf2' // 新增节点ID
			}, {
				id: 3,
				pointName: '示例库-1',
				pointType: 'WAREHOUSE', // 新增类型字段
				locationx: 50, // 原x
				locationy: 150, // 原y
				nodeId: 'rgv.rgv.sdf3' // 新增节点ID
			}];
			maxPointId = 0;
			ElMessage.error(`加载失败,仅展示默认的点位示例`);
		}
	};

	// 选中点位与编辑状态
	const selectedPoint = ref(null);
	const isEditing = ref(false);

	// 缩放相关状态
	const scale = ref(1);

	// 编辑区域拖拽相关状态
	const isPanelDragging = ref(false);
	const panelDragStartPos = reactive({
		x: 0,
		y: 0
	});
	const editorPanel = ref(null);

	// 工具函数：限制数值范围
	const clamp = (value, min, max) => Math.max(min, Math.min(max, value));

	// 限制点位坐标在地图容器范围内
	// 添加缩放比例计算
	const clampX = (value) => {
		if (mapContainer.value) {
			let maxX = (mapContainer.value.offsetWidth - 10) / scale.value;
			return Math.round(clamp(value, 0, maxX));
		}
		return Math.round(value);
	};
	const clampY = (value) => {
		if (mapContainer.value) {
			let maxY = (mapContainer.value.offsetHeight - 10) / scale.value;
			return Math.round(clamp(value, 0, maxY));
		}
		return Math.round(value);
	};
	// 点位样式计算
	const pointStyle = (point) => ({
		left: `${point.locationx * scale.value}px`,
		top: `${point.locationy * scale.value}px`,
		transform: `translate(-50%, -50%) scale(${1/scale.value})` // 保持视觉大小稳定
	});

	// 根据点位名称获取样式类
	const getPointClass = (pointType) => {
		switch (pointType) {
			case 'CAR':
				return 'car-point';
			case 'WAREHOUSE':
				return 'warehouse-point';
			case 'TRANSFER':
				return 'transfer-point';
			default:
				return 'default-point';
		}
	}
	// 拖拽启动
	const startDrag = (point, event) => {
		if (isEditing.value) return;

		isDragging.value = true;
		draggingPoint.value = point;
		// 记录实际坐标属性
		dragStartPos.x = event.clientX - point.locationx * scale.value;
		dragStartPos.y = event.clientY - point.locationy * scale.value;

		// 立即选中该点位
		if (selectedPoint.value?.id !== point.id) {
			selectedPoint.value = point;
		}
	};

	// 拖拽处理
	const handleDrag = (event) => {
		if (!isDragging.value || !mapContainer.value) return;

		let containerRect = mapContainer.value.getBoundingClientRect();
		let rawX = event.clientX - containerRect.left - dragStartPos.x;
		let rawY = event.clientY - containerRect.top - dragStartPos.y;

		let newX = Math.round(rawX / 20) * 20;
		let newY = Math.round(rawY / 20) * 20;
		// 应用坐标限制
		draggingPoint.value.locationx = clampX(newX);
		draggingPoint.value.locationy = clampY(newY);
		// 强制触发数组更新（Vue3 需解构新对象）
		points.value = [...points.value];
	};

	// 停止拖拽
	const stopDrag = () => {
		console.log('无操作，鼠标划过了地图');
		if (draggingPoint.value && draggingPoint.value.id && selectedPoint.value.id) {
			let tuozhuaihou = {
				id: selectedPoint.value.id,
				pointName: selectedPoint.value.pointName,
				pointType: selectedPoint.value.pointType,
				locationX: selectedPoint.value.locationx,
				locationY: selectedPoint.value.locationy,
				nodeId: selectedPoint.value.nodeId
			};
			let response = axios.post('/points/update', tuozhuaihou);
			isDragging.value = false;
			draggingPoint.value = null;
		}

	};

	// 地图点击处理
	const handleMapClick = (event) => {
		if (event.button !== 0 || isDragging.value) return;

		let isClickOnPoint = event.target.closest('.map-point');
		if (isClickOnPoint) return;

		// 获取容器的实际位置
		let containerRect = mapContainer.value.getBoundingClientRect();

		// 将鼠标坐标转换为容器的原始坐标
		let rawX = (event.clientX - containerRect.left) / scale.value;
		let rawY = (event.clientY - containerRect.top) / scale.value;

		// 使用 Math.round 取整
		createNewPoint(Math.round(rawX), Math.round(rawY));
	};

	// 点位点击处理
	const handlePointClick = (point) => {
		selectedPoint.value = point;
	};

	// 创建新点位
	const createNewPoint = (x, y) => {
		let adjustedX = Math.round(x / 20) * 20; // 强制对齐20的倍数
		let adjustedY = Math.round(y / 20) * 20;
		let newId = getNextPointId();
		let newPoint = {
			id: newId,
			pointName: `转转-${newId}`,
			pointType: 'TRANSFER',
			locationx: adjustedX,
			locationy: adjustedY,
			nodeId: '配置KEPServer，获取id'
		};

		points.value.push(newPoint);
		maxPointId = newId; // 更新最大ID

		try {
			let xinzeng = {
				id: newPoint.id,
				pointName: newPoint.pointName,
				pointType: newPoint.pointType,
				locationX: newPoint.locationx,
				locationY: newPoint.locationy,
				nodeId: newPoint.nodeId
			};
			let response = axios.post('/points/insert', xinzeng);
			isEditing.value = false;
			selectedPoint.value = null;
		} catch (error) {
			ElMessage.error('保存失败');
		}
		return newPoint;
	};
	// 获取下一个点位ID
	const getNextPointId = () => {
		return maxPointId + 1;
	};
	// 删除点位
	const confirmDelete = () => {
		if (selectedPoint.value) {
			ElMessageBox.confirm(
					`确定删除 ${selectedPoint.value.pointName} 吗？`,
					'提示', {
						confirmButtonText: '确定',
						cancelButtonText: '取消',
						type: 'warning'
					}
				)
				.then(() => {
					deletePoint(selectedPoint.value.id);
				})
				.catch(() => {
					// 用户点击取消，可根据需要添加提示信息
				});
		}
	};

	const deletePoint = async (id) => {
		console.log('删除点位：' + id);
		try {
			let response = await axios.post('/points/delete', {
				id: id
			});
			console.log('删除点位:', response.data);
			selectedPoint.value = null;
		} catch (error) {
			console.error('删除点位时发生错误:', error);
		}
		console.log('删除成功之后，刷新页面，重新加载点位:');
		loadPoints();

	};
	// 编辑操作
	const startEditing = () => {
		isEditing.value = true;
	};
	// 修改
	const saveChanges = async () => {
		console.log('修改点位的值PointId：' + maxPointId);
		try {
			let xiugai = {
				id: selectedPoint.value.id,
				pointName: selectedPoint.value.pointName,
				pointType: selectedPoint.value.pointType,
				locationX: selectedPoint.value.locationx,
				locationY: selectedPoint.value.locationy,
				nodeId: selectedPoint.value.nodeId
			};
			let response = await axios.post('/points/update', xiugai);

			if (1 == response.data) {
				// console.log(response);
				ElMessage.success('修改成功');
				selectedPoint.value = null;
			}
			isEditing.value = false;
		} catch (error) {
			ElMessage.error('修改失败');
		}
		console.log('更新之后，刷新点位数据');
		loadPoints();
	};

	// 取消编辑
	const cancelEditing = () => {
		isEditing.value = false;
		let original = points.value.find(p => p.id === selectedPoint.value.id);
		Object.assign(selectedPoint.value, original);
	};

	// 消息提示
	const showMessage = (text, type) => {
		ElMessage({
			message: text,
			type: type === 'error' ? 'error' : 'success'
		});
	};

	// 编辑区域拖拽启动
	const startPanelDrag = (event) => {
		isPanelDragging.value = true;
		panelDragStartPos.x = event.clientX - editorPanel.value.offsetLeft;
		panelDragStartPos.y = event.clientY - editorPanel.value.offsetTop;

		document.addEventListener('mousemove', handlePanelDrag);
		document.addEventListener('mouseup', stopPanelDrag);
	};

	// 编辑区域拖拽处理
	const handlePanelDrag = (event) => {
		if (!isPanelDragging.value) return;

		let left = event.clientX - panelDragStartPos.x;
		let top = event.clientY - panelDragStartPos.y;

		editorPanel.value.style.left = `${left}px`;
		editorPanel.value.style.top = `${top}px`;
	};

	// 停止编辑区域拖拽
	const stopPanelDrag = () => {
		isPanelDragging.value = false;
		document.removeEventListener('mousemove', handlePanelDrag);
		document.removeEventListener('mouseup', stopPanelDrag);
	};

	// 获取轨道路径
	const getTrackPath = (track) => {
		let startPoint = points.value.find(p => p.id === track.startPointId);
		let endPoint = points.value.find(p => p.id === track.endPointId);
		if (!startPoint || !endPoint) return '';

		return `M ${startPoint.x * scale.value} ${startPoint.y * scale.value} L ${endPoint.x * scale.value} ${endPoint.y * scale.value}`;
	};


	// 在控制台检查数据结构
	onMounted(() => {
		document.title = '设备管理页面';
		console.log('DOM 已挂载，mapContainer:', mapContainer.value);
		loadPoints();
	});
</script>

<style scoped>
	/* 地图展示区 */
	.map-container {
		position: relative;
		top: 0;
		left: 0;
		width: 100%;
		height: 100%;
		background: #e8eaf6;
		overflow: hidden;
		transform-origin: 0 0;
		transform: scale(v-bind(scale));
		/* 绘制间距为 10 的灰色正方形方格 */
		background-image: linear-gradient(to right, rgba(0, 0, 0, 0.1) 1px, transparent 1px),
			linear-gradient(to bottom, rgba(0, 0, 0, 0.1) 1px, transparent 1px);
		background-size: calc(20px / v-bind(scale)) calc(20px / v-bind(scale));
	}
</style>